package net.WMisiedjan.WirelessRedstone;

import java.util.ArrayList;
import java.util.List;
import java.util.logging.Level;

import net.WMisiedjan.WirelessRedstone.Configuration.WirelessRedstoneConf;
import net.WMisiedjan.WirelessRedstone.Listeners.BlockListen;
import net.WMisiedjan.WirelessRedstone.Listeners.WorldListen;
import net.WMisiedjan.WirelessRedstone.Permissions.*;

import org.bukkit.Chunk;
import org.bukkit.Location;
import org.bukkit.Server;
import org.bukkit.World;
import org.bukkit.event.Event;
import javax.persistence.PersistenceException;
import org.bukkit.plugin.Plugin;
import org.bukkit.plugin.PluginDescriptionFile;
import org.bukkit.plugin.PluginManager;
import org.bukkit.plugin.java.JavaPlugin;

public class WirelessRedstone extends JavaPlugin {
	public static WirelessRedstoneConf config;
	private static StackableLogger logger = new StackableLogger(
			"WirelessRedstone");
	public WireBox WireBox = new WireBox(this);
	public IPermissions permissionsHandler;
	public BlockListen blockListener = new BlockListen(this);
	public WorldListen worldListener = new WorldListen(this);

	public static StackableLogger getLogger() {
		return logger;
	}

	@Override
	public void onDisable() {

	}
	

	@Override
	public void onEnable() {
		PluginDescriptionFile pdfFile = getDescription();
		config = new WirelessRedstoneConf(this.getDataFolder());
		blockListener = new BlockListen(this);
		PluginManager pm = getServer().getPluginManager();
		WirelessRedstone.logger.info(pdfFile.getName() + " version "
				+ pdfFile.getVersion() + " is loading...");
		config.load();
		WirelessRedstone.logger.setLogLevel(config.getLogLevel());
		WirelessRedstone.logger.fine("Loading Permissions...");
		Plugin permissionsPlugin = pm.getPlugin("Permissions");

		// Choosing Permissions it need to be used. Stolen from Essentials.
		// Credits to Essentials Team xd
		if (permissionsPlugin != null) {
			if (permissionsPlugin.getDescription().getVersion().charAt(0) <= '3') {
				this.permissionsHandler = new PPermissions3(permissionsPlugin);
				WirelessRedstone.logger.fine("Using Permissions 3.");
			} else {
				this.permissionsHandler = new PPermissions2(permissionsPlugin);
				WirelessRedstone.logger.fine("Using Permissions 2.");
			}

			WirelessRedstone.logger.info("Detected Permissions version "
					+ permissionsPlugin.getDescription().getVersion());
		} else {
			WirelessRedstone.logger
					.info("No Permissions Detected! Defaulting to OP/Config files!.");
			this.permissionsHandler = new opPermissions(this);
		}

		WirelessRedstone.logger.fine("Loaded Permissions...");
		config.save();

		this.WireBox.UpdateChacheNoThread();

		WirelessRedstone.logger.info("Registering Events...");
		pm.registerEvent(Event.Type.SIGN_CHANGE, this.blockListener,
				Event.Priority.Normal, this);
		pm.registerEvent(Event.Type.REDSTONE_CHANGE, this.blockListener,
				Event.Priority.High, this);
		pm.registerEvent(Event.Type.BLOCK_BREAK, this.blockListener,
				Event.Priority.Normal, this);
		pm.registerEvent(Event.Type.CHUNK_UNLOAD, this.worldListener,
				Event.Priority.Normal, this);
		pm.registerEvent(Event.Type.BLOCK_FROMTO, this.blockListener,
				Event.Priority.Normal, this);
		pm.registerEvent(Event.Type.BLOCK_PHYSICS, this.blockListener,
				Event.Priority.Normal, this);

		WirelessRedstone.logger.fine("Registering commands...");
		getCommand("wrhelp").setExecutor(new WirelessCommands(this));
		getCommand("wrr").setExecutor(new WirelessCommands(this));
		getCommand("wrt").setExecutor(new WirelessCommands(this));
		getCommand("wrremove").setExecutor(new WirelessCommands(this));
		getCommand("wrc").setExecutor(new WirelessCommands(this));

		WirelessRedstone.logger.fine("Loading Chunks");
		LoadChunks();

		System.out.println(pdfFile.getName() + " version "
				+ pdfFile.getVersion() + " is enabled!");
	}

	public void LoadChunks() {
		if (WirelessRedstone.config.isCancelChunkUnloads()) {
			for (IWirelessPoint loc : this.WireBox.getAllSigns()) {
				Location location = WireBox.getPointLocation(loc);
				Chunk center = location.getBlock().getChunk();
				World world = center.getWorld();
				int range = WirelessRedstone.config.getChunkUnloadRange();
				for (int dx = -(range); dx <= range; dx++) {
					for (int dz = -(range); dz <= range; dz++) {
						Chunk chunk = world.getChunkAt(center.getX() + dx,
								center.getZ() + dz);
						world.loadChunk(chunk);
					}
				}
			}
		}
	}
}
